﻿using RiskMan.DataClass.Models.NotBasModels;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
using System.Runtime.Serialization;
using System.Text;

namespace RiskMan.DataClass.Models.Sterling
{
    /// <summary>
    /// Класс элементов робота для Стерлинг
    /// </summary>
    [Serializable]
    public class SterlingItem : INotifyPropertyChanged, ISerializable
    {
        #region private

        //Базовые настройки
        private string _account;
        private string _clientCode;
        private string _instrument;
        private string _ecn;
        private bool _isRun;
        private Guid _guidRobot;
        private string _comment;
        //рабочие настройки робота
        private double _priceOpen;
        private double _deviation; //отклонение 0,3%
        private bool _deviationBool; //отклонение 0,3%
        private double _deviationStartRobot; //отклонение при старте робота
        private bool _deviationStartRobotBool; //отклонение при старте робота

        private double _initialStop;
        private double _breakeven;      
        private double _changePrice2;
        private double _priceClosePoz;
        private double _moveStop;

        private int _numberBreakevenStop;
        private DateTime _timeCancelRepeatOpen;
        private DateTime _timeKillAndClosePoz;



        private int _quantity;
        private int _curPosition;
        private string _operation;
        private double _priceOpenPoz;
        private double _lastPrice;
        private double _prevLastPrice;

        private int _numberOfAttempt;
        private int _curNumberOfAttempt;
        private ObservableCollection<TradesOpen> _tradeList;

        #endregion

        #region public

        
        /// <summary>
        /// Велична, на которую выставляется первоначальный стоп
        /// </summary>
        public double InitialStop
        {
            get { return _initialStop; }
            set
            {
                if (_initialStop != value)
                {
                    _initialStop = value;
                    RaisePropertyChanged("InitialStop");
                }
            }
        }
           

        /// <summary>
        /// уровень стопа на котором сейчас стоит стоп
        /// </summary>
        public int NumberBreakevenStop
        {
            get { return _numberBreakevenStop; }
            set
            {
                if (_numberBreakevenStop != value)
                {
                    _numberBreakevenStop = value;
                    RaisePropertyChanged("NumberBreakevenStop");
                }
            }
        }

        /// <summary>
        /// Время, после которого запрещен повторный вход в позицию
        /// </summary>
        public DateTime TimeCancelRepeatOpen
        {
            get { return _timeCancelRepeatOpen; }
            set
            {
                if (_timeCancelRepeatOpen != value)
                {
                    _timeCancelRepeatOpen = value;
                    RaisePropertyChanged("TimeCancelRepeatOpen");
                }
            }
        }

        /// <summary>
        /// Время, после которого снимаются все аткивные заявки и стоп-заявки и закрывается позиция
        /// </summary>
        public DateTime TimeKillAndClosePoz
        {
            get { return _timeKillAndClosePoz; }
            set
            {
                if (_timeKillAndClosePoz != value)
                {
                    _timeKillAndClosePoz = value;
                    RaisePropertyChanged("TimeKillAndClosePoz");
                }
            }
        }
        /// <summary>
        /// цена активации стоп-заявки для входа в позицию
        /// </summary>
        public double PriceOpen
        {
            get { return _priceOpen; }
            set
            {
                if (_priceOpen != value)
                {
                    _priceOpen = value;
                    RaisePropertyChanged("PriceOpen");
                }
            }
        }
        /// <summary>
        /// Отклонение цены входа от цены активации стоп-заявки для входа
        /// </summary>
        public double Deviation
        {
            get { return _deviation; }
            set
            {
                if (_deviation != value)
                {
                    _deviation = value;
                    RaisePropertyChanged("Deviation");
                }
            }
        }
        /// <summary>
        /// Было отклонение при входе в позицию роботом от цены заявки за сегодня или нет
        /// </summary>
        public bool DeviationBool
        {
            get { return _deviationBool; }
            set
            {
                if (_deviationBool != value)
                {
                    _deviationBool = value;
                    RaisePropertyChanged("DeviationBool");
                }
            }
        }
        /// <summary>
        /// отклонение цены при активации робота
        /// </summary>
        public double DeviationStartRobot
        {
            get { return _deviationStartRobot; }
            set
            {
                if (_deviationStartRobot != value)
                {
                    _deviationStartRobot = value;
                    RaisePropertyChanged("DeviationStartRobot");
                }
            }
        }

        /// <summary>
        /// Было отклонение при статрте робота за сегодня или нет
        /// </summary>
        public bool DeviationStartRobotBool
        {
            get { return _deviationStartRobotBool; }
            set
            {
                if (_deviationStartRobotBool != value)
                {
                    _deviationStartRobotBool = value;
                    RaisePropertyChanged("DeviationStartRobotBool");
                }
            }
        }
        /// <summary>
        /// Торговый счет
        /// </summary>
        public string Account
        {
            get { return _account; }
            set
            {
                if (_account != value)
                {
                    _account = value;
                    RaisePropertyChanged("Account");
                }
            }
        }

        /// <summary>
        /// Комментарий последнего действия робота
        /// </summary>
        public string Comment
        {
            get { return _comment; }
            set
            {
                if (_comment != value)
                {
                    _comment = value;
                    RaisePropertyChanged("Comment");
                }
            }
        }

        /// <summary>
        /// Счет депо
        /// </summary>
        public string ClientCode
        {
            get { return _clientCode; }
            set
            {
                if (_clientCode != value)
                {
                    _clientCode = value;
                    RaisePropertyChanged("ClientCode");
                }
            }
        }

        /// <summary>
        /// Торгуемый инструмент
        /// </summary>
        public string Instrument
        {
            get { return _instrument; }
            set
            {
                if (_instrument != value)
                {
                    _instrument = value;
                    RaisePropertyChanged("Instrument");
                }
            }
        }

        /// <summary>
        /// ECN
        /// </summary>
        public string ECN
        {
            get { return _ecn; }
            set
            {
                if (_ecn != value)
                {
                    _ecn = value;
                    RaisePropertyChanged("ECN");
                }
            }
        }

        /// <summary>
        /// Запуск/остановка работы по данному инструменту
        /// </summary>
        public bool IsRun
        {
            get { return _isRun; }
            set
            {
                if (_isRun != value)
                {
                    _isRun = value;
                    RaisePropertyChanged("isRun");
                }
            }
        }

        /// <summary>
        /// Величина на которую должны уйти цена от цены сделки, чтоб стоп переставился в безубыток
        /// </summary>
        public double Breakeven
        {
            get { return _breakeven; }
            set
            {
                if (_breakeven != value)
                {
                    _breakeven = value;
                    RaisePropertyChanged("Breakeven");
                }
            }
        }
        /// <summary>
        /// величина на которой будет закрыта позиция.
        /// </summary>
        public double PriceClosePoz
        {
            get { return _priceClosePoz; }
            set
            {
                if (_priceClosePoz != value)
                {
                    _priceClosePoz = value;
                    RaisePropertyChanged("PriceClosePoz");
                }
            }
        }
        /// <summary>
        /// Величина, на которую перместиться стоп, при изменение цены на заданную величину (изменение цены 2), от цены сделки
        /// </summary>
        public double MoveStop
        {
            get { return _moveStop; }
            set
            {
                if (_moveStop != value)
                {
                    _moveStop = value;
                    RaisePropertyChanged("ThirdBreakeven");
                }
            }
        }

        /// <summary>
        /// Величина на которую должны уйти цена от цены сделки, чтоб стоп переставился на величину переноса стопа
        /// </summary>
        public double ChangePrice2
        {
            get { return _changePrice2; }
            set
            {
                if (_changePrice2 != value)
                {
                    _changePrice2 = value;
                    RaisePropertyChanged("ChangePrice2");
                }
            }
        }

        /// <summary>
        /// Количество контрактов/лотов, в одной выставляемой заявке
        /// </summary>
        public int Quantity
        {
            get { return _quantity; }
            set
            {
                if (_quantity != value)
                {
                    _quantity = value;
                    RaisePropertyChanged("Quantity");
                }
            }
        }

        /// <summary>
        /// текущая позиция по уровню и инструменту
        /// </summary>
        public int CurPosition
        {
            get { return _curPosition; }
            set
            {
                if (_curPosition != value)
                {
                    _curPosition = value;
                    RaisePropertyChanged("CurPosition");
                }
            }
        }


        /// <summary>
        /// Вид операции по инструменту
        /// </summary>
        public string Operation
        {
            get { return _operation; }
            set
            {
                if (_operation != value)
                {
                    _operation = value;
                    RaisePropertyChanged("Operation");
                }
            }
        }
        /// <summary>
        /// Цена открытия позиции
        /// </summary>
        public double PriceOpenPoz
        {
            get { return _priceOpenPoz; }
            set
            {
                if (_priceOpenPoz != value)
                {
                    _priceOpenPoz = value;
                    RaisePropertyChanged("PriceOpenPoz");
                }
            }
        }

        /// <summary>
        /// Количество попыток для входа
        /// </summary>
        public int NumberOfAttempt
        {
            get { return _numberOfAttempt; }
            set
            {
                if (_numberOfAttempt != value)
                {
                    _numberOfAttempt = value;
                    RaisePropertyChanged("NumberOfAttempt");
                }
            }
        }
        /// <summary>
        /// текущее значение попыток
        /// </summary>
        public int CurNumberOfAttempt
        {
            get { return _curNumberOfAttempt; }
            set
            {
                if (_curNumberOfAttempt != value)
                {
                    _curNumberOfAttempt = value;
                    RaisePropertyChanged("CurNumberOfAttempt");
                }
            }
        }
        /// <summary>
        /// коллекция активнных и исполненных сделок на открытие и закрытие позиции
        /// </summary>
        public ObservableCollection<TradesOpen> TradeList
        {
            get { return _tradeList; }
            set
            {
                if (_tradeList != value)
                {
                    _tradeList = value;
                    RaisePropertyChanged("TradeList");
                }
            }
        }

      
        /// <summary>
        /// цена последней сделки
        /// </summary>
        public double LastPrice
        {
            get { return _lastPrice; }
            set
            {
                if (_lastPrice != value)
                {
                    _lastPrice = value;
                    RaisePropertyChanged("LastPrice");
                }
            }
        }

        /// <summary>
        /// цена предпоследней сделки
        /// </summary>
        public double PrevLastPrice
        {
            get { return _prevLastPrice; }
            set
            {
                if (_prevLastPrice != value)
                {
                    _prevLastPrice = value;
                    RaisePropertyChanged("PrevLastPrice");
                }
            }
        }

        /// <summary>
        /// уникальный номер уровня, чтоб не терялся при сортировке
        /// </summary>
        public Guid GuidRobot
        {
            get { return _guidRobot; }
            set
            {
                if (_guidRobot != value)
                {
                    _guidRobot = value;
                    RaisePropertyChanged("GuidRobot");
                }
            }
        }



     

        #endregion

        public SterlingItem() { }

        #region event PropertyChangedEventHandler

        public event PropertyChangedEventHandler PropertyChanged;

        protected void RaisePropertyChanged(string propertyName)
        {
            var handler = PropertyChanged;
            if (handler != null)
            {
                handler(this, new PropertyChangedEventArgs(propertyName));
            }
        }

        #endregion

        public SterlingItem(SerializationInfo info, StreamingContext context)
        {
            IsRun = info.GetBoolean("isRun");
            Account = info.GetString("Account");
            ClientCode = info.GetString("ClientCode");
            Instrument = info.GetString("Instrument");
            ECN = info.GetString("ECN");
            GuidRobot = (Guid)info.GetValue("GuidRobot", typeof(Guid));

            PriceOpen = info.GetDouble("PriceOpen");
            Deviation = info.GetDouble("Deviation");
            DeviationStartRobot = info.GetDouble("DeviationStartRobot");
            Breakeven = info.GetDouble("Breakeven");
            PriceClosePoz = info.GetDouble("PriceClosePoz");
            ChangePrice2 = info.GetDouble("ChangePrice2");
            MoveStop = info.GetDouble("MoveStop");
            InitialStop = info.GetDouble("InitialStop");
            TimeCancelRepeatOpen = info.GetDateTime("TimeCancelRepeatOpen");
            TimeKillAndClosePoz = info.GetDateTime("TimeKillAndClosePoz");

            Quantity = info.GetInt32("Quantity");
            Operation = info.GetString("Operation");

            NumberOfAttempt = info.GetInt32("NumberOfAttempt");
            
        }

        public void GetObjectData(SerializationInfo info, StreamingContext context)
        {
            info.AddValue("isRun", IsRun);
            info.AddValue("Account", Account);
            info.AddValue("ClientCode", ClientCode);
            info.AddValue("Instrument", Instrument);
            info.AddValue("ECN", ECN);
            info.AddValue("GuidRobot", GuidRobot);

            info.AddValue("PriceOpen", PriceOpen);
            info.AddValue("Deviation", Deviation);
            info.AddValue("DeviationStartRobot", DeviationStartRobot);
            info.AddValue("InitialStop", InitialStop);
            info.AddValue("Breakeven", Breakeven);
            info.AddValue("PriceClosePoz", PriceClosePoz);
            info.AddValue("ChangePrice2", ChangePrice2);
            info.AddValue("MoveStop", MoveStop);
            info.AddValue("TimeCancelRepeatOpen", TimeCancelRepeatOpen);
            info.AddValue("TimeKillAndClosePoz", TimeKillAndClosePoz);

            info.AddValue("Quantity", Quantity);
            info.AddValue("Operation", Operation);

            info.AddValue("NumberOfAttempt", NumberOfAttempt);

        }
    }
}
